home *** CD-ROM | disk | FTP | other *** search
/ NOVA - For the NeXT Workstation / NOVA - For the NeXT Workstation.iso / Documents / NeXTAnswers / objc.584 < prev    next >
Text File  |  1992-02-06  |  6KB  |  146 lines

  1. {\rtf0\ansi{\fonttbl\f2\fnil Times-Roman;\f0\fmodern Courier;\f1\fswiss Helvetica;}
  2. \paperw11760
  3. \paperh7200
  4. \margl120
  5. \margr120
  6. {\colortbl\red0\green0\blue0;}
  7. \pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\f2\b0\i0\ul0\fs28\fc0 C++ integration\
  8. \
  9. Q:  Can I integrate C++ code into my Interface Builder/Objective-C application?  How?\
  10. \
  11. A:  Yes, in release 2.0 you can, and it's pretty easy (once you know how)!  The procedure breaks down into three categories of things that you must do: compiling, Interface Builder and getting the two languages to talk to each other.\
  12. \
  13.  
  14. \b Compiling
  15. \b0 \
  16. First, you must use the C++ compiler for 
  17. \i all
  18. \i0  of your source files--including the Objective-C sources.  To do this, add the following line to your Makefile.preamble:\
  19.  
  20. \f0     \
  21.     CC=cc++\
  22.  
  23. \f2 \
  24. Now that you are using the C++ compiler, you have to notify the compiler when/if your header files contain non-C++ code.  For Objective-C header files, encapsulate your 
  25. \f0 #import
  26. \f2  directives like this:\
  27. \
  28.     
  29. \f0 extern "Objective-C"        \
  30.     \{                \
  31.     #import <appkit/Application.h>\
  32.     #import <appkit/Panel.h>\
  33.     #import <appkit/TextField.h>\
  34.     #import <appkit/Button.h>\
  35.     \}\
  36.  
  37. \f2 \
  38. For regular C header files, encapsulate your 
  39. \f0 #import
  40. \f2  directives like this: \
  41. \
  42.  
  43. \f0     extern "C"\
  44.     \{\
  45.     #import <appkit/publicWraps.h>\
  46.     #import <objc/error.h>\
  47.     #import <objc/NXStringTable.h>\
  48.     #import <strings.h>\
  49.     \}\
  50.     \
  51.  
  52. \pard\tx620\tx1240\tx1860\tx2480\tx3100\tx3720\tx4340\tx4980\tx5600\tx6220\f2\fc0 The C++ "linkage" directive serves two purposes (when importing interface files that contain straight ANSI-C/Objective-C code). It:\
  53. \
  54.  
  55. \pard\tx960\tx1920\tx2880\tx3840\tx4800\tx5760\tx6720\tx7680\tx8640\tx9600 • 
  56. \pard\tx620\tx1240\tx1860\tx2480\tx3100\tx3720\tx4340\tx4980\tx5600\tx6220\fc0  allows you to link with libraries that have not been compiled with the C++ compiler. Since libraries on the NeXT computer are compiled  with the Objective-C compiler (cc, not cc++), you must use the C++ linkage directive when importing interface files that represent NeXT  libraries (or any library that is not compiled with cc++). \
  57. \
  58.  
  59. \pard\tx960\tx1920\tx2880\tx3840\tx4800\tx5760\tx6720\tx7680\tx8640\tx9600 • 
  60. \pard\tx620\tx1240\tx1860\tx2480\tx3100\tx3720\tx4340\tx4980\tx5600\tx6220\fc0   tells the compiler to ignore C++ keywords that will result in syntax errors when importing ANSI-C
  61. \pard\tx960\tx1920\tx2880\tx3840\tx4800\tx5760\tx6720\tx7680\tx8640\tx9600\fc0  or 
  62. \pard\tx620\tx1240\tx1860\tx2480\tx3100\tx3720\tx4340\tx4980\tx5600\tx6220\fc0 Objective-C interface files.  The linkage directive essentially tells the C++ compiler to treat keywords (such as 
  63. \pard\tx960\tx1920\tx2880\tx3840\tx4800\tx5760\tx6720\tx7680\tx8640\tx9600\fc0 the method names 
  64. \pard\tx620\tx1240\tx1860\tx2480\tx3100\tx3720\tx4340\tx4980\tx5600\tx6220\fc0 "new", "delete", etc.) as normal identifiers.\
  65.  
  66. \pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\fc0 \
  67.  
  68. \b Interface Builder\
  69.  
  70. \b0 Within Interface Builder you need to add the C++ 
  71. \b .c
  72. \b0  and 
  73. \b .h
  74. \b0  files to your project.  Add the files separately--the 
  75. \b .c
  76. \b0  file goes in the 
  77. \b .c
  78. \b0  category, and the 
  79. \b .h
  80. \b0  file goes in the 
  81. \b .h
  82. \b0  (other) category. \
  83. \
  84. If you already have a 
  85. \b _main.m
  86. \b0  file, make sure that the option in Interface Builder for generating the main file is turned 
  87. \i off
  88. \i0 .  Then, remove the void declaration of the main procedure by replacing:\
  89.  
  90. \pard\tx520\tx1060\tx1600\tx2120\tx2660\tx3200\tx3720\tx4260\tx4800\tx5320\f0\fc0     void main(int argc, char *argv[]) \{
  91. \fs24 \
  92.  
  93. \pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\f2\fs28\fc0 with:\
  94.  
  95. \pard\tx520\tx1060\tx1600\tx2120\tx2660\tx3200\tx3720\tx4260\tx4800\tx5320\f1\fs24\fc0      
  96. \f0\fs28 main(int argc, char *argv[]) \{
  97. \fs24 \
  98.  
  99. \pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\f2\fs28\fc0 \
  100. \
  101.  
  102. \b Modifying Source Code
  103. \b0 \
  104. Since the nib files generated by Interface Builder are based the appkit, and it generates source templates in Objective-C, we must envision our program such that Objective-C and nib files are the foundation of our program, and the C++ code is a supporting library.\
  105. \
  106. Now that we can compile, we need to get an Objective-C object and a C++ object to pass messages to one another.  Suppose that we have two created objects--a C++ object and an Objective-C object.  This is how you
  107. \b  
  108. \b0 would refer to the C++ object and tell it to "do something":\
  109.     
  110. \pard\tx620\tx1240\tx1860\tx2480\tx3100\tx3720\tx4340\tx4980\tx5600\tx6220\fc0     
  111. \pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\fc0 \
  112.         
  113. \pard\tx620\tx1240\tx1860\tx2480\tx3100\tx3720\tx4340\tx4980\tx5600\tx6220\f0\fc0 class CalcEngine     *cplus_object;    \
  114.  
  115. \pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\fc0         cplus_object = new CalcEngine;\
  116.  
  117. \f2         
  118. \f0 cplus_object->doSomething();
  119. \f2 \
  120.         \
  121.  C++ objects are implemented as regular C structures, so to access public instance variables, or public methods of a C++ object, you dereference the object with the -> syntax as you would a structure member. And this is how you would refer to an Objective-C object from C++:\
  122.         \
  123.         
  124. \f0 id objectiveObj;\
  125.         \
  126.         objectiveObj = [ObjectiveObjCls new];\
  127.         [objectiveObj doSomethingElse:what];\
  128.  
  129. \f2 \
  130. Basically, in either case you use the language constructs of the object to which you are referring, and embed them in the source file of the other language.\
  131.     \
  132.  
  133. \b Example
  134. \b0 \
  135. There is an example located in /NextDeveloper/Examples/Calculator++ which illustrates the integration of Interface Builder nib files, Objective-C source code, and C++ source code into one program.\
  136. \
  137. QA584\
  138. \
  139.  
  140. \pard\tx960\tx1920\tx2880\tx3840\tx4800\tx5760\tx6720\tx7680\tx8640\tx9600 Valid for 2.0\
  141.  
  142. \pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\fc0 \
  143. See also NextAnswers 591.\
  144. \
  145.  
  146.